<script setup lang="ts">
import { inject, onMounted, provide, ref } from 'vue'
import { setMenuPosition, tidyUp, deleteById } from '@/api/desktop/MenuApi'
import { getAssetsResource } from '@/utils/resource'
import { MenuType, UserConfig } from '@/views/desktop/type/index.ts'
import MenuDialog from '@/views/desktop/dialog/MenuDialog.vue'
import DictDialog from '@/views/desktop/dialog/DictDialog.vue'
import WallpaperDialog from '@/views/desktop/dialog/WallpaperDialog.vue'
import ContextMenu from '@imengyu/vue3-context-menu'
import UserConfigDialog from '@/views/desktop/dialog/UserConfigDialog.vue'
import AppStoreDialog from '@/views/desktop/dialog/AppStoreDialog.vue'
import Note from '@/views/desktop/widget/Note.vue'

const menus = inject('menus')
let appInit = inject('initDesk')
let dialogVisible = inject('dialogVisible')
let bottomMenus = inject('bottomMenus')
let notes = inject('notes')

let menu = ref<MenuType>(new MenuType())
let userConfig = inject('userConfig', ref<UserConfig>(new UserConfig()))
let currentMenu = ref<MenuType>(new MenuType())

const initDesk = () => {
  appInit()
  menu.value = new MenuType()
}

initDesk()

provide('menu', menu)

const dragStart = (e: any) => {
  e.preventDefault()
}

let iconClickMap = {
  '1': () => {
    // 添加菜单的弹出框
    dialogVisible.value['1'] = true
  },
  '1721373518305026049': (item) => {
    // 添加字典的弹出框
    let index = bottomMenus.value.findIndex((item) => item.id == item.id)
    if (index < 0) {
      bottomMenus.value.push(item)
    }
    currentMenu.value = item
    dialogVisible.value['1721373518305026049'] = true
  },
  '1725038231098339330': () => {
    // 一键整理
    tidyUp().then(() => {
      initDesk()
    })
  },
  '1725090062755225601': (item) => {
    // 壁纸
    currentMenu.value = item
    dialogVisible.value['1725090062755225601'] = true
  },
  '1730057603960832001': (item) => {
    // 用户设置
    currentMenu.value = item
    dialogVisible.value['1730057603960832001'] = true
  },
  '1719380640589168641': (item: MenuType) => {
    // 应用商店
    currentMenu.value = item
    dialogVisible.value['1719380640589168641'] = true
  },
}

let isDrag = ref(true)
const iconClick = (item: MenuType) => {
  if (!isDrag.value) {
    if (item.openModel == '_blank') {
      window.open(item.linkUrl, item.openModel)
    } else {
      iconClickMap[item.id](item)
    }
  }
}

const draggable = () => {
  for (let menu of menus.value) {
    addDraggable(menu)
  }

  for (let note of notes.value) {
    addDraggable(note)
  }
}

const addDraggable = (item) => {
  // 开始拖动的位置
  let dragStartX = 0
  let dragStartY = 0
  let startX = 0
  let startY = 0
  const clickDurationTime = 200
  let clickStartTime = 0
  let clickEndTime = 0

  let el = document.getElementById(item.id)
  el.addEventListener('mousedown', function (e) {
    clickStartTime = Date.now()
    document.addEventListener('mouseup', handleMouseUp)
    const mousedownHandler = () => {
      if (isDrag.value) {
        // 获取元素相对于视窗的位置
        e.preventDefault()
        const rect = e.target.getBoundingClientRect()
        // 设置鼠标的起始位置
        startX = e.clientX - rect.left
        startY = e.clientY - rect.top
        // 添加mousemove和mouseup事件监听器，用于处理拖动和释放的操作
        // 保存开始拖动的位置
        document.addEventListener('mousemove', handleMouseMove)
      }
    }
    function handleMouseMove(e) {
      dragStartX = e.clientX - startX
      dragStartY = e.clientY - startY
      // 通过改变元素的position属性来移动元素
      el.style.position = 'absolute'
      el.style.zIndex = '1000'
      el.style.left = `${dragStartX}px`
      el.style.top = `${dragStartY}px`
    }
    setTimeout(mousedownHandler, clickDurationTime)

    // 结束拖动的操作
    function handleMouseUp() {
      clickEndTime = Date.now()
      isDrag.value = clickEndTime - clickStartTime > clickDurationTime
      document.removeEventListener('mousemove', handleMouseMove)
      document.removeEventListener('mouseup', handleMouseUp)
      if (isDrag.value) {
        let params = {
          id: el.id,
          positionX: el.style.left,
          positionY: el.style.top,
        }
        setMenuPosition(params)
      }
      clearTimeout(mousedownHandler)
    }
  })
}

const menuRightClick = (item, type, e) => {
  let props = []
  if (type == 'add') {
    props = [
      {
        label: '新增',
        onClick: () => {
          // 获取点击点的位置
          menu.value.positionX = e.x + 'px'
          menu.value.positionY = e.y + 'px'
          iconClickMap['1']()
        },
      },
      {
        label: '刷新',
        onClick: () => {
          window.location.href = window.location.href
        },
      },
    ]
  } else if (type == 'edit' || type == 'delete') {
    props = [
      {
        label: '修改',
        onClick: () => {
          menu.value = item
          if (!isDrag.value) {
            iconClickMap['1']()
          }
        },
      },
      {
        label: '删除',
        onClick: () => {
          menu.value = item
          // todo 二次确认
          deleteById(item.id).then((res) => {
            initDesk()
          })
        },
      },
    ]
  }

  // 获取点击的位置
  ContextMenu.showContextMenu({
    x: e.x,
    y: e.y,
    items: props,
  })
}

const getCurrentMenu = (id): MenuType => {
  return menus.value.filter((item) => item.id == id)[0]
}

onMounted(() => {
  setTimeout(() => {
    draggable()
  }, 200)
})

const getBackgroundImg = () => `/bing${userConfig.value.backgroundImg}`
</script>

<template>
  <div
    id="container"
    @contextmenu.prevent.stop="menuRightClick(null, 'add', $event)"
    class="h-90 grid-layout"
    :style="{
      backgroundImage: 'url(' + getBackgroundImg() + ')',
    }"
  >
    <div
      draggable="true"
      :ondragstart="dragStart"
      v-for="item in menus"
      class="m-5 h-max w-max cursor-pointer flex flex-col justify-center items-center"
      :id="item.id"
      :style="item.position"
      @click="iconClick(item)"
      @contextmenu.prevent.stop="menuRightClick(item, 'edit', $event)"
    >
      <img
        v-if="item.iconType == 100000000202"
        :src="item.iconUrl"
        class="h-10 w-10"
        alt=""
      />
      <img
        v-if="item.iconType == 100000000201"
        :src="getAssetsResource(item.iconUrl)"
        class="h-10 w-10"
        alt=""
      />
      <span class="text-xs mt-2" :style="{ color: userConfig.fontColor }">
        {{ item.name }}
      </span>
    </div>

    <div
      draggable="true"
      :ondragstart="dragStart"
      v-for="item in notes"
      class="cursor-pointer"
      :style="item.position"
      :id="item.id"
    >
      <note :note="item" class="relative w-96" />
    </div>
  </div>

  <menu-dialog @initDesk="initDesk" />
  <dict-dialog
    v-if="dialogVisible['1721373518305026049']"
    :menu="getCurrentMenu('1721373518305026049')"
  />

  <wallpaper-dialog
    v-if="dialogVisible['1725090062755225601']"
    :menu="getCurrentMenu('1725090062755225601')"
  />

  <user-config-dialog
    v-if="dialogVisible['1730057603960832001']"
    :menu="getCurrentMenu('1730057603960832001')"
  />
  <app-store-dialog
    v-if="dialogVisible['1719380640589168641']"
    :menu="getCurrentMenu('1719380640589168641')"
    :title="'应用商店'"
  />
</template>

<style scoped>
.h-90 {
  height: 95%;
}
.grid-layout {
  display: grid;
  grid-template-columns: repeat(auto-fill, 5rem);
  gap: 1rem;
  grid-template-rows: repeat(auto-fill, 5rem);
}
</style>
